/*
 * Copyright © 2017-2019 Cask Data, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
 * use this file except in compliance with the License. You may obtain a copy of
 * the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations under
 * the License.
 */

package io.cdap.wrangler.api.lineage;

/**
 * This class enumerates the mutation types that are allowed when collecting
 * column mutations within a directive.
 */
public enum MutationType {
  /**
   * When the values of a column impact one or more other columns it is labeled
   * as a READ column.
   *
   * <p>
   *   As example
   *   <code>copy <source> <destination></code>.
   *   In this case since the values of the entries of the source column are
   *   read in order to produce the destination column, the source column should
   *   be labeled as READ.
   * </p>
   *
   * <p>
   *   <code>filter-row-if-matched <column> <regex></code>.
   *  In this case since the values of the entries of the supplied column are read
   *  in order to filter the rows in the dataset, column should be labeled as READ.
   *  This is the case even though the supplied column is modified since its values
   *  are read.
   * </p>
   */
  READ(1),

  /**
   * When a column is generated by the directive, this column is labeled as an ADD column.
   *
   * <p>Ex1. <code>copy <source> <destination></code>. In this case since the destination
   * is a new column that is generated by this directive, it should be labeled as ADD. </p>
   */
  ADD(2),

  /**
   * When a column is dropped as a result of the directive, this column is labeled as a
   * DROP column.
   *
   * <p><code>drop <column>[,<column>*]</code>. In this case since all the columns
   * listed are dropped by this directive, all the listed columns should be labled as
   * DROP columns.</p>
   */
  DROP(3),

  /**
   * When the name of a column is changed to another name, both the old and new name are
   * labeled as RENAME columns. Note that neither column is labeled as ADD or DROP since
   * no column is added or dropped, bu t instead a column's name is being replaced in place.
   *
   * <p><code>rename <old> <new></code>. In this case since the name old is being replaced
   * with the name new, both old and new should be labeled as RENAME. This is because one
   * column's name is being changed/renamed from old to new. </p>
   *
   * <p><code>swap <column1> <column2></code>. In this case since both the name column1
   * and the name column2 are simply being replaced with the other, both column1 and column2
   * should be labeled as RENAME. No records are being added or lost by this directive.</p>
   */
  RENAME(4),

  /**
   * When a column is being modified.
   */
  MODIFY(5);

  // Integer representation of the mutation.
  private final int type;

  MutationType(int type) {
    this.type = type;
  }

  /**
   * @return Integer representation of <code>MutationType</code>.
   */
  public int getType() {
    return type;
  }
}
